package com.atguigu.tingshu.album.service.impl;

import cn.hutool.core.date.DateUtil;
import cn.hutool.core.io.file.FileNameUtil;
import cn.hutool.core.util.IdUtil;
import cn.hutool.log.Log;
import com.atguigu.tingshu.album.config.MinioConstantProperties;
import com.atguigu.tingshu.album.service.AuditService;
import com.atguigu.tingshu.album.service.FileUploadService;
import com.atguigu.tingshu.common.execption.GuiguException;
import io.minio.MinioClient;
import io.minio.PutObjectArgs;
import io.minio.errors.*;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;

import javax.imageio.ImageIO;
import java.awt.image.BufferedImage;
import java.io.IOException;
import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;
import java.util.Arrays;
import java.util.HashSet;
import java.util.Set;

@Service
public class FileUploadServiceImpl implements FileUploadService {
    private static final Logger log = LoggerFactory.getLogger(FileUploadServiceImpl.class);
    @Autowired
    private MinioClient minioClient;
    @Autowired
    private MinioConstantProperties minioConstantProperties;
    @Autowired
    private AuditService auditService;

//检查，上传图片接口
    @Override
    public String fileUpLoad(MultipartFile multipartFile) {

        //1.业务校验验证图片内容格式是否合法
        try {
            //把图片转为bufferedImage对象
            //imageio验证图片格式
            BufferedImage bufferedImage = ImageIO.read(multipartFile.getInputStream());
            if (bufferedImage==null){
                throw new GuiguException(400,"文件格式有误，请重试");
            }
            //2.业务校验-验证图片大小合法,长height 宽 width
            int width = bufferedImage.getWidth();
            int height = bufferedImage.getHeight();
            if (width>900||height>900){
                throw new GuiguException(400,"图片尺寸过大，宽和高需小于900像素");
            }

        // 对图片审核
        //对图片内容进行校验是否合法
        String suggestion = auditService.auditImage(multipartFile);
        if ("review".equals(suggestion) || "block".equals(suggestion)) {
            throw new GuiguException(500, "图片内容不合法");
        }

        //上传minio
        //3.1 生成带有文件夹目录文件名称 形式：/日期/随机文件名称.后缀
            String folder = "/" +DateUtil.today();
            String fileName = IdUtil.randomUUID();
            String extName = FileNameUtil.extName(multipartFile.getOriginalFilename());
            String objName =  folder + "/" + fileName + "." + extName;
            //3.2 调用minio客户对象上传文件方法
            String bucketName = minioConstantProperties.getBucketName();

            minioClient.putObject(PutObjectArgs.builder()
                    .bucket(bucketName)
                    .object(objName)
                    .stream(multipartFile.getInputStream(),multipartFile.getSize(),-1)
                    .contentType(multipartFile.getContentType())
                    .build());
            //3.3 拼接上传文件在线路径地址
            return minioConstantProperties.getEndpointUrl()+ "/"+bucketName + objName;

        } catch (Exception e) {
            log.error("文件上传失败", e);
            throw new GuiguException(500, e.getMessage());
        }

    }
}
